package com.bestdata.TD440.datahandle.service;


import com.bestdata.TD440.datahandle.model.Map;
import com.bestdata.TD440.datahandle.model.Queue;
import com.bestdata.TD440.util.CRC16Util;
import com.bestdata.TD440.util.Hex2Float;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.annotation.DependsOn;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

/**
 * @author chizhenyu
 * @title:
 * @description: 接收DMS的数据
 * @date 2019-12-2 13:51:50
 */

@Component
@DependsOn("springContextHolder")
public class DataReceiveProcess extends Thread{

    private Logger logger = LoggerFactory.getLogger(this.getClass());

    private final boolean keep = true;
    private final Integer XOR = -1;

    private DataReceiveProcess() {
        new Thread(this).start();
    }

    /**
     * 服务启动
     */
    public synchronized void startServer() {
        try {
            this.start();
        }catch(Exception ex) {

        }
    }
    @Override
    public void run() {
        this.startServer();
    }

    /**
     * 1-4:55aa  开始标志位
     * 5-8:00c4  长度
     * 9-10:02  版本号
     * 11-12:0e  CMD
     * 13-16:0001  序列号
     * 17-54:45363330313230313930393231313535313032 设备ID （E630120190921155102）
     *
     * 55-56:00  通道
     * 57-60:0032  频率
     * 61-68:5f1f8068  时间  秒
     * 69-75:000b82db  时间  微妙
     *
     * 76-196：   data(根据是否开启上传数据通道)
     * 后4位： crc校验
     */
    public void start(){
        while(keep){

            String oriMsg = "";
            try {
                oriMsg = Queue.dataQueue.take();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }

            if(StringUtils.isEmpty(oriMsg)){
                logger.error("oriMsg is null !!");
                continue;
            }

            try {
                //解析设备ID
                String devID = oriMsg.substring(16, 54);

                //todo 如若需要实际设备ID，解开注释即可
//                List<String> arrDevID = new ArrayList<>();
//
//                for (int i = 0; i < devID.length(); i++) {
//                    arrDevID.add(devID.substring(i,i+2));
//                    i = i+1;
//                }
//                //得到转码后的设备ID
//                devID = Hex2Float.ASCII2HexStr(arrDevID.toArray());
                //处理粘包导致的数据异常
                String[] dataList = oriMsg.split("55AA");

                //处理数据原始报文中粘包现象
                for (int j = 1; j < dataList.length; j++) {
                    String resData = "55AA"+dataList[j];
                    logger.info(resData+"");

                    //todo crc校验
                    Integer xor = CRC16Util.CRC16XOR(resData);

                    if(XOR != xor){
                        logger.info("Incorrect check code, abnormal data"+resData);
                        continue;
                    }

                    //解析报文数据
                    String data = resData.substring(76, resData.length() - 4);

                    //确保报文中含有振动采集值
                    if (data.length() % 4 == 0) {
                        char[] chars = data.toCharArray();
                        String temp = "";
                        //循环取出data报文中每个元素
                        for (int i = 1; i <= chars.length; i++) {
                            temp += chars[i - 1];
                            if (i % 8 == 0) {
                                //取出振动值
                                String HexData = Hex2Float.bytes2Float(temp);

                                if(Double.parseDouble(HexData) > 100.0){
                                    logger.error("msg -> {}",oriMsg);
                                    logger.error("data msg -> {}",data);
                                }

                                if(Double.parseDouble(HexData) > 10000.0){
                                    continue;
                                }
                                //通过设备ID查询Map存储器中是否包含
                                String val = (String) Map.dMap.get(devID);

                                if (StringUtils.isEmpty(val)) {
                                    //新增记录
                                    Map.dMap.put(devID, HexData);
                                } else {
                                    //更新为当前时间段内最大值最大值
                                    if (Double.parseDouble(HexData) > Double.parseDouble(val)) {

                                        Map.dMap.put(devID, HexData);
                                    }
                                }
                                temp = "";
                            }
                        }
                    }
                }

            } catch (Exception e) {
                logger.error(oriMsg+"data handle is bad!!!  "+e);
                e.printStackTrace();
            }
        }
    }
}

